//
//  LHAPI.swift
//  SwiftRequest
//
//  Created by Pro on 2020/2/12.
//  Copyright © 2020 Pro. All rights reserved.
//

import Foundation
import Alamofire

enum LHHTTPMethod {
    case GET
    case POST
}


//add1
protocol LHDataClient {
    var host: String { get }
    func send<T :LHRequest>(_ r : T, handler: @escaping(T.Response?)->Void)
}


//replease5
//protocol JNRequest {
//
//        var host : String {get}
//       var path : String {get}
//       var method : HPHTTPMethod {get}
//       var parameter: [String: Any] { get }
//
//       associatedtype Response
//       func parse(data: NSDictionary) -> Response?
//
//
//}


protocol LHRequest {
   
    var path : String {get}
    var method : LHHTTPMethod {get}

    var parameter: [String: Any] { get }
    
    associatedtype Response : Decodable
}

//protocol LHRequest {
//    var host : String {get}
//    var path : String {get}
//    var method : LHHTTPMethod {get}
//    var parameter: [String: Any] { get }
//
//    associatedtype Response
//    func parse(data: NSDictionary) -> Response?
//}

struct LHlhRequest: LHRequest {
    typealias Response = RestanurantTotal
//    hidden2
//    var host: String  {
//        return "https://apis.map.qq.com/ws/place/v1/"
////        ?region=北京&keyword=美食&key=OB4BZ-D4W3U-B7VVO-4PJWW-6TKDJ-WPB77
//    }
    var path: String {
        return "suggestion/"
    }
    let method: LHHTTPMethod = .GET
    var parameter: [String : Any]
}
//
//extension LHRequest {
//    func sendRequest(hander:@escaping(Response?)->Void) {
//        //...
//        let url = self.host + r.path
//        Alamofire.request(url, method: HTTPMethod.get, parameters: self.parameter).responseJSON { (response) in
//                    switch response.result {
//                    case .success(let data):
//                           let dic = data as? NSDictionary
//                           if let res = self.parse(data: dic!) {
//                            hander(res)
//                         }else {
//                            hander(nil)
//                         }
//                        case .failure:
//                            hander(nil)
//                    }
//                }
//          }
//}


extension LHlhRequest {
    
    func parse(data: NSDictionary) -> RestanurantTotal? {
        return RestanurantTotal(data:data)
    }
}

//add3
struct LHAlamofireClient {
   
    static let `default` = LHAlamofireClient()

   var host: String  {
       return "https://apis.map.qq.com/ws/place/v1/"
   }
   func send<T :LHRequest>(_ r : T, handler: @escaping(T.Response?)->Void) {

           let url = self.host + r.path
    Alamofire.request(url, method:HTTPMethod.get, parameters: r.parameter).responseJSON { (response) in
               switch response.result {
               case .success(let data):
//                change7
//                   let dic = data as? NSDictionary
//
//                   if let res = r.parse(data: dic!) {
//                       handler(res)
//                   }else {
//                       handler(nil)
//                   }
                if let dic = data as? NSDictionary {
                    if let res = T.Response.parse(data: dic) {
                        handler(res)
                    }else {
                        handler(nil)
                    }
                }else {
                    handler(nil)
                }

               case .failure:
                   handler(nil)
               }
           }
   }
}


//add4
protocol Decodable {
//   static func parse(data : NSDictionary)->Self?
    static func parse(data : DecodeType)->Self?

}

//add6
extension RestanurantTotal : Decodable {
   static func parse(data: DecodeType) -> RestanurantTotal? {
       return RestanurantTotal(data: data.asDictionary()!)
   }
}


struct LHLocalClient {
    
    var host: String  {
        return ""
    }
    func send<T :LHRequest>(_ r : T, handler: @escaping(T.Response?)->Void) {
        
        switch r.path {
        case "suggestion/":
            let fileURL = Bundle.main.path(forResource: "response", ofType: "json")
           
//            if let data = try? String.init(contentsOfFile: fileURL!, encoding: .utf8) {
//                let jsonData:Data = data.data(using: .utf8)!
//                if let dic = try? JSONSerialization.jsonObject(with: jsonData, options: .mutableContainers) {
//                    if let res = T.Response.parse(data: dic as! NSDictionary) {
//                         handler(res)
//                    }else {
//                         handler(nil)
//                    }
//                }else {
//                    handler(nil)
//                }
//            }
            
            if let data = try? String.init(contentsOfFile: fileURL!, encoding: .utf8) {
                            let jsonData:Data = data.data(using: .utf8)!
                            if let res = T.Response.parse(data: jsonData) {
                                    handler(res)
                            }else {
                                    handler(nil)
                            }
                        }else
            {
                
                handler(nil)
            }
        default:
            handler(nil)
        }
    }
}



protocol DecodeType {
    func asDictionary() -> NSDictionary?;
}

extension NSDictionary : DecodeType {
    func asDictionary() -> NSDictionary? {
        return self
    }
}

extension Data : DecodeType {
   func asDictionary() -> NSDictionary? {
      if let dic = try? JSONSerialization.jsonObject(with: self, options: .mutableContainers) {
        return dic as? NSDictionary
      }
    return nil
   }
}


